﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Text;
using System.Threading.Tasks;
using Fast.Framework.Models;


namespace Fast.Framework.Interfaces
{

    #region IQuery1
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    public interface IQuery<T, TDbOptions> where TDbOptions : DbOptions
    {

        /// <summary>
        /// 查询建造者
        /// </summary>
        IQueryBuilder QueryBuilder { get; }

        /// <summary>
        /// 作为
        /// </summary>
        /// <param name="tableName">表名称</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> As(string tableName);

        /// <summary>
        /// 不同
        /// </summary>
        /// <returns></returns>
        IQuery<T, TDbOptions> Distinct();

        /// <summary>
        /// 左连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> LeftJoin<T2>(Expression<Func<T, T2, bool>> expression);

        /// <summary>
        /// 内连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> InnerJoin<T2>(Expression<Func<T, T2, bool>> expression);

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> Where(Expression<Func<T, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="inFieldsName">In字段名称</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> In<FieldsType>(string inFieldsName, params FieldsType[] values);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="inFieldsName">In字段名称</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> In<FieldsType>(string inFieldsName, List<FieldsType> values);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> In<FieldsType>(Expression<Func<T, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="notInFieldsName">Not In字段名称</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> NotIn<FieldsType>(string notInFieldsName, params FieldsType[] values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="notInFieldsName">Not In字段名称</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> NotIn<FieldsType>(string notInFieldsName, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> NotIn<FieldsType>(Expression<Func<T, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="orderFiledsName">排序字段名称</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> OrderBy(string orderFiledsName, string orderType = "ASC");

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> GroupBy(Expression<Func<T, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> Having(Expression<Func<T, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, TDbOptions> OrderBy(Expression<Func<T, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, TResult>> expression);

        /// <summary>
        /// 第一异步
        /// </summary>
        /// <returns></returns>
        Task<T> FirstAsync();

        /// <summary>
        /// 字典异步
        /// </summary>
        /// <returns></returns>
        Task<Dictionary<string, object>> DictionaryAsync();

        /// <summary>
        /// 字典列表异步
        /// </summary>
        /// <returns></returns>
        Task<List<Dictionary<string, object>>> DictionaryListAsync();

        /// <summary>
        /// 到列表异步
        /// </summary>
        /// <returns></returns>
        Task<List<T>> ToListAsync();

        /// <summary>
        /// 到分页列表
        /// </summary>
        /// <param name="page">页</param>
        /// <param name="pageSize">页大小</param>
        /// <returns></returns>
        Task<PageData<List<T>>> ToPageListAsync(int page, int pageSize);

        /// <summary>
        /// 计数异步
        /// </summary>
        /// <returns></returns>
        Task<int> CountAsync();

        /// <summary>
        /// 任何异步
        /// </summary>
        /// <returns></returns>
        Task<bool> AnyAsync();
    }
    #endregion

    #region IQuery2
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <typeparam name="T2"></typeparam>
    public interface IQuery<T, T2, TDbOptions> : IQuery<T, TDbOptions> where TDbOptions : DbOptions
    {
        /// <summary>
        /// 左连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> LeftJoin<T3>(Expression<Func<T, T2, T3, bool>> expression);

        /// <summary>
        /// 内连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> InnerJoin<T3>(Expression<Func<T, T2, T3, bool>> expression);

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> Where(Expression<Func<T, T2, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> In<FieldsType>(Expression<Func<T, T2, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> NotIn<FieldsType>(Expression<Func<T, T2, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> GroupBy(Expression<Func<T, T2, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> Having(Expression<Func<T, T2, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, T2, TDbOptions> OrderBy(Expression<Func<T, T2, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, T2, TResult>> expression);
    }
    #endregion

    #region IQuery3
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <typeparam name="T2"></typeparam>
    /// <typeparam name="T3"></typeparam>
    /// <typeparam name="TDbOptions"></typeparam>
    public interface IQuery<T, T2, T3, TDbOptions> : IQuery<T, T2, TDbOptions> where TDbOptions : DbOptions
    {
        /// <summary>
        /// 左连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> LeftJoin<T4>(Expression<Func<T, T2, T3, T4, bool>> expression);

        /// <summary>
        /// 内连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> InnerJoin<T4>(Expression<Func<T, T2, T3, T4, bool>> expression);

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> Where(Expression<Func<T, T2, T3, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> In<FieldsType>(Expression<Func<T, T2, T3, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> NotIn<FieldsType>(Expression<Func<T, T2, T3, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> GroupBy(Expression<Func<T, T2, T3, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> Having(Expression<Func<T, T2, T3, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, T2, T3, TDbOptions> OrderBy(Expression<Func<T, T2, T3, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, T2, T3, TResult>> expression);

    }
    #endregion

    #region IQuery4
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <typeparam name="T2"></typeparam>
    /// <typeparam name="T3"></typeparam>
    /// <typeparam name="T4"></typeparam>
    /// <typeparam name="TDbOptions"></typeparam>
    public interface IQuery<T, T2, T3, T4, TDbOptions> : IQuery<T, T2, T3, TDbOptions> where TDbOptions : DbOptions
    {
        /// <summary>
        /// 左连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> LeftJoin<T5>(Expression<Func<T, T2, T3, T4, T5, bool>> expression);

        /// <summary>
        /// 内连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> InnerJoin<T5>(Expression<Func<T, T2, T3, T4, T5, bool>> expression);

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> Where(Expression<Func<T, T2, T3, T4, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> In<FieldsType>(Expression<Func<T, T2, T3, T4, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> NotIn<FieldsType>(Expression<Func<T, T2, T3, T4, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> GroupBy(Expression<Func<T, T2, T3, T4, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> Having(Expression<Func<T, T2, T3, T4, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, TDbOptions> OrderBy(Expression<Func<T, T2, T3, T4, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, T2, T3, T4, TResult>> expression);

    }
    #endregion

    #region IQuery5
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <typeparam name="T2"></typeparam>
    /// <typeparam name="T3"></typeparam>
    /// <typeparam name="T4"></typeparam>
    /// <typeparam name="T5"></typeparam>
    /// <typeparam name="TDbOptions"></typeparam>
    public interface IQuery<T, T2, T3, T4, T5, TDbOptions> : IQuery<T, T2, T3, T4, TDbOptions> where TDbOptions : DbOptions
    {
        /// <summary>
        /// 左连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> LeftJoin<T6>(Expression<Func<T, T2, T3, T4, T5, T6, bool>> expression);

        /// <summary>
        /// 内连接
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> InnerJoin<T6>(Expression<Func<T, T2, T3, T4, T5, T6, bool>> expression);

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> Where(Expression<Func<T, T2, T3, T4, T5, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> In<FieldsType>(Expression<Func<T, T2, T3, T4, T5, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> NotIn<FieldsType>(Expression<Func<T, T2, T3, T4, T5, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> GroupBy(Expression<Func<T, T2, T3, T4, T5, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> Having(Expression<Func<T, T2, T3, T4, T5, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, TDbOptions> OrderBy(Expression<Func<T, T2, T3, T4, T5, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, T2, T3, T4, T5, TResult>> expression);

    }
    #endregion

    #region IQuery6
    /// <summary>
    /// 查询接口类
    /// </summary>
    /// <typeparam name="T"></typeparam>
    /// <typeparam name="T2"></typeparam>
    /// <typeparam name="T3"></typeparam>
    /// <typeparam name="T4"></typeparam>
    /// <typeparam name="T5"></typeparam>
    /// <typeparam name="T6"></typeparam>
    /// <typeparam name="TDbOptions"></typeparam>
    public interface IQuery<T, T2, T3, T4, T5, T6, TDbOptions> : IQuery<T, T2, T3, T4, T5, TDbOptions> where TDbOptions : DbOptions
    {

        /// <summary>
        /// 条件
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> Where(Expression<Func<T, T2, T3, T4, T5, T6, bool>> expression);

        /// <summary>
        /// In条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> In<FieldsType>(Expression<Func<T, T2, T3, T4, T5, T6, object>> expression, List<FieldsType> values);

        /// <summary>
        /// NotIn条件
        /// </summary>
        /// <typeparam name="FieldsType">字段类型</typeparam>
        /// <param name="expression">表达式</param>
        /// <param name="values">值</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> NotIn<FieldsType>(Expression<Func<T, T2, T3, T4, T5, T6, object>> expression, List<FieldsType> values);

        /// <summary>
        /// 分组
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> GroupBy(Expression<Func<T, T2, T3, T4, T5, T6, object>> expression);

        /// <summary>
        /// 有
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> Having(Expression<Func<T, T2, T3, T4, T5, T6, bool>> expression);

        /// <summary>
        /// 排序
        /// </summary>
        /// <param name="expression">表达式</param>
        /// <param name="orderType">排序类型</param>
        /// <returns></returns>
        IQuery<T, T2, T3, T4, T5, T6, TDbOptions> OrderBy(Expression<Func<T, T2, T3, T4, T5, T6, object>> expression, string orderType = "ASC");

        /// <summary>
        /// 选择
        /// </summary>
        /// <typeparam name="TResult"></typeparam>
        /// <param name="expression">表达式</param>
        /// <returns></returns>
        IQuery<TResult, TDbOptions> Select<TResult>(Expression<Func<T, T2, T3, T4, T5, T6, TResult>> expression);

    }
    #endregion
}
